#include "Time.hpp"

#ifdef CH32
extern "C" void SysTick_Handler(void) __attribute__((interrupt("WCH-Interrupt-fast")));
void SysTick_Handler(void)
{
}
Time::Time(/* args */)
{
    NVIC_SetPriority(SysTicK_IRQn, 0x10);
    NVIC_EnableIRQ(SysTicK_IRQn);
    SysTick->CTLR = 0;
    SysTick->SR = 0;
    SysTick->CNT = 0;
    SysTick->CMP = 0xFFFFFFFFFFFFFFFF;
    SysTick->CTLR = 0xf;
}

Time::~Time()
{
    NVIC_DisableIRQ(SysTicK_IRQn);
    SysTick->CTLR = 0;
    SysTick->SR = 0;
    SysTick->CNT = 0;
}
float Time::getTime()
{
    return SysTick->CNT / 144000000.0f;
}
#endif

#ifdef AT32
volatile uint32_t systimes;
extern "C" void TMR2_GLOBAL_IRQHandler(void)
{
    if (tmr_flag_get(TMR2, TMR_OVF_FLAG) != RESET)
    {
        systimes++;
        tmr_flag_clear(TMR2, TMR_OVF_FLAG);
    }
}
Time::Time()
{
    systimes = 0;
    crr_periph_clock_enable(CRR_TMR2_PERIPH_CLOCK, TRUE);
    tmr_32_bit_function_enable(TMR2, TRUE);
    /* tmr2 time base configuration */
    tmr_base_init(TMR2, 2399, 0);
    tmr_cnt_dir_set(TMR2, TMR_COUNT_UP);
    tmr_clock_source_div_set(TMR2, TMR_CLOCK_DIV1);
    tmr_interrupt_enable(TMR2, TMR_OVF_INT, TRUE);
    nvic_irq_enable(TMR2_GLOBAL_IRQn, 8, 0);
    tmr_counter_enable(TMR2, TRUE);
}

Time::~Time()
{
    crr_periph_reset(CRR_TMR2_PERIPH_RESET, TRUE);
}

float Time::getTime()
{
    return systimes * 0.00001f;
}
#endif

#ifdef STM32

volatile uint32_t systimes; 
extern TIM_HandleTypeDef htim3;
extern "C" void TIM3_IRQHandler(void)
{
    if (__HAL_TIM_GET_FLAG(&htim3, TIM_FLAG_UPDATE) != RESET)
    {
        if (__HAL_TIM_GET_IT_SOURCE(&htim3, TIM_FLAG_UPDATE) != RESET)
        {
            {
                systimes++;
                __HAL_TIM_CLEAR_IT(&htim3, TIM_FLAG_UPDATE);
            }
        }
    }
}
Time::Time()
{
    htim3.Instance = TIM3;
    htim3.Init.Prescaler = 0;
    htim3.Init.CounterMode = TIM_COUNTERMODE_UP;
    htim3.Init.Period = 1679;
    htim3.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
    htim3.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_DISABLE;
    if (HAL_TIM_Base_Init(&htim3) != HAL_OK)
    {
        Error_Handler();
    }
    systimes = 0;
    HAL_TIM_Base_Start_IT(&htim3);
}

Time::~Time()
{
    __HAL_RCC_TIM3_FORCE_RESET();
}

float Time::getTime()
{
    return systimes * 0.00001f;
}
#endif